package com.sss.hloster0306;

import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.Method;

public class TestNewInstance {

	public static void main(String[] args) {
		test04();
	}

	private static void test01() {
		try {
			Class c = Class.forName("com.sss.hloster0306.Super");
			// 通过Class 类的newInstance() 方法创建对象(需要强制类型转换)
			Super sup = (Super) c.newInstance();// newInstance 方法要求该Class对应类需要有无参构造方法？？？
			// Super sup = new Super();//同上句等价
			System.out.println(sup.supPublic());
		} catch (Exception e) {

			e.printStackTrace();
		}
	}

	private static void test02() {
		try {
			Class c = Class.forName("com.sss.hloster0306.Super");
			// 返回一个指定参数列表（int.class,int class）的Constructor对象
			Constructor con = c.getDeclaredConstructor(new Class[] { int.class, int.class });
			// 通过Constructor的newInstance(Object[] arge)方法创建对象，参数为对象列表
			// 参数列表对基本数据类型支持自动装箱、拆箱，所以也可以写成newInstance（21,22）
			Super sup = (Super) con.newInstance(new Object[] { 21, 22 });
			System.out.println(sup.supPackege());

			// 返回一个无参的Constructor对象
			Constructor con2 = c.getDeclaredConstructor();
			// 通过Constructor的newInstance() 方法创建无参对象
			Super sup2 = (Super) con2.newInstance();
			System.out.println(sup2.supProtected());
		} catch (Exception e) {

			e.printStackTrace();
		}
	}

	/**
	 * 修改属性
	 */
	private static void test03() {
		try {
			Class c = Class.forName("com.sss.hloster0306.Super");
			Super sup = (Super) c.newInstance();
			// 通过属性名称获得Field对象
			Field f = c.getDeclaredField("supPri");// supPri为私有属性
			// 取消属性的访问权限控制，即使private 属性也可以进行访问
			f.setAccessible(true);
			// 调用get(object o)方法取得对象o 对应属性值
			System.out.println("取消访问权限控制后访问 supPri ，其值为 ： " + f.get(sup));
			// 调用set（Object o ,Object v ） 方法设置对象 o 对应属性值
			f.set(sup, 20);
			System.out.println("f.set(sup,20)后访问supPri   ,  其值为 ： " + f.get(sup));
		} catch (Exception e) {
			e.printStackTrace();
		}
	}

	public int add(int x, int y) {
		return x + y;
	}

	public int add(int x) {
		return x + 1;
	}

	public int multiply(int x, int y) {
		return x * y;
	}

	public int multiply(int x) {
		return x * x;
	}

	/**
	 * 调用方法
	 */
	private static void test04() {
		try {
			Class c = TestNewInstance.class;
			Object obj = c.newInstance();
			// 通过方法名，参数名类型列表，获得Method对象
			Method m = c.getDeclaredMethod("multiply", new Class[] { int.class });
			// invoke(Object o,Object[] args )方法调用对象 o 对应方法
			System.out.println("调用方法：multiply,输入值为 int型 3，结果为：：" + m.invoke(obj, new Object[] { 3 }));
			Method m2 = c.getDeclaredMethod("add", new Class[] { int.class ,int.class});
			System.out.println("调用方法：add,输入值为int型18，结果为：" + m2.invoke(obj, new Object[] { 18,12}));
		} catch (Exception e) {
			e.printStackTrace();
		}
	}
}
